﻿using System;
using UnityEngine;
using System.Collections;
using System.Collections.Generic;
using System.Diagnostics;
using System.Text;
using Inlycat.Log;

namespace Inlycat
{

    /// <summary>
    /// Author:gouzhun
    /// </summary>
    public class TimeFlagManager : Singleton<TimeFlagManager>
    {
        private TimeFlagManager()
        {
#if suntabu_timeflag
        Enable = true;
#endif
            if (Enable)
            {
                m_Stopwatch = new Stopwatch();
                m_FlagDic = new Dictionary<string, Dictionary<string, List<TimeFlag>>>();
                m_Stopwatch.Start();
            }

        }

        private Stopwatch m_Stopwatch;

        /// <summary>
        /// key1: module name
        /// key2: flag name
        /// </summary>
        private Dictionary<string, Dictionary<string, List<TimeFlag>>> m_FlagDic;




        public bool Enable = true;


        private void DefaultLogAction()
        {

        }

        public void Reset()
        {
            if (Enable)
            {
                m_Stopwatch.Reset();
                m_FlagDic.Clear();
            }
        }

        public void CallDIYQueryAction(Action<string, string, Action<string>> diyQueryAction, string moduleName, string flagName, Action<string> onLog)
        {
            diyQueryAction(moduleName, flagName, onLog);
        }

        public void SetTimeFlag(string module, string flag, FlagState flagState, Action logAction = null)
        {
            if (Enable)
            {
                TimeFlag tf = new TimeFlag()
                {
                    ModuleName = module,
                    FlagName = flag,
                    SetTime = m_Stopwatch.ElapsedMilliseconds,
                    CurrentFPSCount = Time.frameCount,
                    FlagState = flagState,
                    LogAction = logAction
                };

                if (m_FlagDic.ContainsKey(module))
                {
                    var dic = m_FlagDic[module];
                    if (dic.ContainsKey(flag))
                    {
                        var list = dic[flag];
                        list.Add(tf);
                    }
                    else
                    {
                        dic[flag] = new List<TimeFlag>() { tf };
                    }
                }
                else
                {
                    m_FlagDic[module] = new Dictionary<string, List<TimeFlag>>()
                {
                    {flag,new List<TimeFlag>(){tf}}
                };
                }

                if (tf.LogAction == null)
                {
                    tf.LogAction = DefaultLogAction;
                }
                tf.LogAction();
            }
        }

        #region General Query Action List

        public static void FlagProcessTime(string moduleName, string flag, Action<string> onLog)
        {
            var sb = new StringBuilder();
            if (TimeFlagManager.Instance.m_FlagDic.ContainsKey(moduleName))
            {
                var moduleDic = Instance.m_FlagDic[moduleName];
                var each = 0f;
                var moduleAll = 0f;
                if (string.IsNullOrEmpty(flag))
                {
                    // 此种情况就获取整个模块的flag
                    foreach (var key in moduleDic.Keys)
                    {
                        var flagList = moduleDic[key];
                        if (flagList.Count == 2)
                        {
                            each = flagList[1].SetTime - flagList[0].SetTime;
                            sb.Append(string.Format("Flag:{0}\t time:{1}", key, each));
                            moduleAll += each;
                        }
                    }
                    sb.Append(string.Format("Module:{0}\t allTime:{1}", moduleName, moduleAll));
                }
                else
                {
                    if (moduleDic.ContainsKey(flag))
                    {
                        var flagList = moduleDic[flag];
                        each = flagList[1].SetTime - flagList[0].SetTime;
                        sb.Append(string.Format("Flag:{0}\t time:{1}", flag, each));
                    }
                }
            }
            onLog(sb.ToString());
        }

        #endregion


        public void LogData()
        {
            foreach (Dictionary<string, List<TimeFlag>> item in m_FlagDic.Values)
            {
                foreach (List<TimeFlag> timeFlags in item.Values)
                {
                    foreach (var timeFlag in timeFlags)
                    {
                        PLog.Log(timeFlag.ToString());
                    }
                }
            }

        }

    }


    public class TimeFlag
    {
        public string ModuleName;

        public string FlagName;

        public long SetTime;

        public long CurrentFPSCount;

        public FlagState FlagState;

        public Action LogAction;

        public override string ToString()
        {
            StringBuilder sb = new StringBuilder();
            sb.Append(string.Format(
                "Module: {0}\t Flag: {1}\t SetTime: {2}\t FPSInx: {3}\t FlagState: {4}\t LogAction: {5}", ModuleName,
                FlagName, SetTime, CurrentFPSCount, FlagState, LogAction == null ? "null" : LogAction.ToString()));
            return sb.ToString();
        }
    }

    public enum FlagState
    {
        Start,
        Finish,
    }


}